package net.liteheaven.xblib.plugin;

import android.app.Activity;
import android.app.Instrumentation;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.text.TextUtils;

import net.liteheaven.hidefix.ReflectionHelper;

import java.lang.reflect.Field;
import java.lang.reflect.Method;

public class PluginUtil {

    /**
     * 挂钩Instrumentation
     */
    static boolean hookInstrumentation(){
        boolean result = false;
        try{
            Class<?> activityThread = Class.forName("android.app.ActivityThread");
            Method currentActivityThread = ReflectionHelper.getDeclaredMethod(activityThread,
                    "currentActivityThread");
            currentActivityThread.setAccessible(true);
            Object activityThreadObject = currentActivityThread.invoke(null);

            Field mInstrumentation = ReflectionHelper.getDeclaredField(activityThread, "mInstrumentation");
            mInstrumentation.setAccessible(true);
            Instrumentation instrumentation = (Instrumentation) mInstrumentation.get(activityThreadObject);
            InstrumentationWrapper customInstrumentation = new InstrumentationWrapper(instrumentation);
            mInstrumentation.set(activityThreadObject, customInstrumentation);
            result = true;
        }catch (Exception e){
            XPluginLog.i(e);
        }
        XPluginLog.i("hook Instrumentation result = " + result);
        return result;
    }

    /**
     * 类在初始包中
     */
    static boolean isInInitialPackage(Context context, String className){
        boolean result;
        try {
            ClassLoader classLoader = context.getApplicationContext().getClassLoader();
            classLoader.loadClass(className);
            result = true;
        } catch (ClassNotFoundException e) {
            result = false;
        } catch (Exception e){
            XPluginLog.i(e);
            result = true;
        }
        return result;
    }

    /**
     * 主要处理以包外Activity为对象的意图
     */
    static void handleOutwardIntent(Context context, Intent intent) {
        if (intent == null || context == null){
            return;
        }

        IntentHandler ih = PluginKit.getInstance().getIntentHandler();

        ComponentName componentName = intent.getComponent();
        if (componentName != null){
            String className = componentName.getClassName();
            if (!TextUtils.isEmpty(className)){
                boolean inPackage = PluginUtil.isInInitialPackage(context, className);
                if (!inPackage){
                    ih.markAsPlugin(context, intent);
                }
            }
        }

        if (context instanceof Activity){
            Activity activity = (Activity)context;
            Intent ai = activity.getIntent();
            if (ai != null){
                String pluginName = ai.getStringExtra(XPluginConst.PLUGIN_NAME);
                if (!TextUtils.isEmpty(pluginName)){
                    ih.attachPlugin(pluginName, intent);
                }
            }
        }
    }
}
